<?php
/**
 * Celebrio timer using logging
 *
 * @copyright  Copyright (c) 2012 Celebio Software, s.r.o.
 * @package    Kernel
 */
namespace Celebrio\Diagnostics;

use Nette\Object;

use \Celebrio\Logging\Logger;
use KernelModule\LogsModule\PerformanceModule\LogLevelManager;

/**
 * Celebrio timer using logging
 *
 * @author Martin Novák
 */
class Timer extends Object {
	/**
	 * request ID identifies unique server request
	 * @var float
	 */
	private static $requestID = NULL;
	/**
	 * @var array
	 */
	private static $blocks = array();
	/**
	 * @var Microsoft_WindowsAzure_Storage_Table
	 */
	private static $instance;
	/**
	 * (TimerLevel::REQUEST | TimerLevel::OVERVIEW | default TimerLevel::DETAILED)
	 * @var int
	 */
	private static $watchedLevel = 10000;

    private function __construct()
    {
    	self::$watchedLevel = LogLevelManager::getCurrent();
    	trigger_error('Construct is not allowed.', E_USER_ERROR);
    }
    
    /**
     * 
     * Starts Celebrio timer
     * @param String $block
     * @param int $level (TimerLevel::REQUEST | TimerLevel::OVERVIEW | default TimerLevel::DETAILED)
     */
    public static function start($block,$level = 30000)
    {
    	if (self::$requestID === NULL) {
    		self::$requestID = microtime(true);
    	}
    	if($level <= self::$watchedLevel){
    		// we add name space and class name to the block name to avoid colisions
    		$debug = debug_backtrace();
    		if(isset($debug[1]["class"])) {
    			$block = $block ." [". $debug[1]["class"] ."]";
    		}

    		if(strpos($block, "§")) {
    			// '§' character is used as a separator in local file logs
    			throw new \NotSupportedException("Block cannot contain '§' character.");
    		}
    		
    		if(isset(self::$blocks[$block])) {
                \Logger::getRootLogger()->error("There is already a block named ".htmlspecialchars($block)." in Timer.");
    		}

    		self::$blocks[$block] = microtime(true);
    	}
    }
    
    /**
     * 
     * Stops Celebrio timer and loggs the value using log4php TIMER logger
     * @param string $block
     */
    public static function stop($block)
    {
    	// we add name space and class name to the block name to avoid colisions
    	$debug = debug_backtrace();
    	if(isset($debug[1]["class"])) {
    		$block = $block ." [". $debug[1]["class"] ."]";
    	}

    	if(isset(self::$blocks[$block])){
    		$time = microtime(true) - self::$blocks[$block];
    		unset(self::$blocks[$block]);
    		\Logger::getLogger("timer")->debug(array(self::$requestID,$block,$time));
    	}
    }

    public function __clone()
    {
        trigger_error('Clone is not allowed.', E_USER_ERROR);
    }

    public function __wakeup()
    {
        trigger_error('Unserializing is not allowed.', E_USER_ERROR);
    }
}
